import { Injectable } from "@nestjs/common";
import { InjectRepository } from "@nestjs/typeorm";
import { User } from "./entities/user.entity";
import { FindConditions, Like, Repository } from "typeorm";
import { ReqAddUserDto, ReqUpdateUserDto, ReqUserListDto } from "./dto/req-user.dto";
import { PaginatedDto } from "src/common/dto/paginated.dto";
import { Dept } from "../dept/entities/dept.entity";
import { RoleService } from "../role/role.service";
import { DeptService } from "../dept/dept.service";
import { SharedService } from "src/shared/shared.service";
import { ResUserListDto } from "./dto/res-user.dto";
import { InjectRedis, Redis } from "@nestjs-modules/ioredis";
import { USER_VERSION_KEY } from "src/common/constants/redis.constant";

@Injectable()
export class UserService {
  constructor(
    @InjectRepository(User) private readonly userRepository: Repository<User>,
    private readonly roleService: RoleService,
    private readonly deptService: DeptService,
    private readonly sharedService: SharedService,
    @InjectRedis() private readonly redis: Redis,
  ) {}

  /**
   * @description: 通过用户名获取用户
   * @param {string} username
   * @return {*}
   */
  async findOneByUsername(username: string) {
    const user = await this.userRepository
      .createQueryBuilder("user")
      .select("user.userId")
      .addSelect("user.username")
      .addSelect("user.password")
      .addSelect("user.salt")
      .addSelect("user.dept")
      .leftJoinAndSelect("user.dept", "dept")
      .where({
        username: username,
      })
      .getOne();

    return user;
  }

  /**
   * @description: 通过id查询用户的所有信息，排除删除的
   * @param {number} userId
   * @return {*}
   */
  async findOneUserAllById(userId: number): Promise<User> {
    const user: User = await this.userRepository
      .createQueryBuilder("user")
      .leftJoinAndSelect("user.dept", "dept", "dept.del_flag = 0")
      .leftJoinAndSelect("user.roles", "role", "role.delFlag = 0")
      .where({
        userId,
        delFlag: "0",
      })
      .getOne();

    return user;
  }

  // 分页查询
  async getUserList(reqUserListDto: ReqUserListDto): Promise<PaginatedDto<ResUserListDto>> {
    let where: FindConditions<User> = {
      delFlag: "0",
    };
    if (reqUserListDto.username) {
      where.username = Like(`%${reqUserListDto.username}%`);
    }
    const dept_id = reqUserListDto.dept_id;
    const queryBuilder = this.userRepository
      .createQueryBuilder("user")
      .innerJoin("user.dept", "dept")
      .select("user.userId", "userId")
      .addSelect("user.username", "username")
      .addSelect("user.nick_name", "nick_name")
      .addSelect("user.create_time", "create_time")
      .addSelect("user.remark", "remark")
      .addSelect("dept.dept_id", "dept_id")
      .addSelect("dept.dept_name", "dept_name")
      .skip(reqUserListDto.skip)
      .take(reqUserListDto.take)
      .andWhere(where)
      .andWhere("dept.dept_id = :dept_id", { dept_id });

    const count = await queryBuilder.getCount();
    const result = await queryBuilder.getRawMany();

    for (let i = 0; i < result.length; i++) {
      const item = result[i];
      const roles = await this.roleService.getRolesByUserId(item.userId);
      item.roleObjs = roles;
    }

    return {
      list: result,
      totalNum: count,
      pageNum: reqUserListDto.pageNum,
      pageSize: reqUserListDto.pageSize,
    };
  }

  // 新增用户
  async addUser(reqAddUserDto: ReqAddUserDto) {
    // 1.通过部门id获取部门
    const dept = await this.deptService.getDeptById(reqAddUserDto.dept_id);
    // 2.通过角色数组获取角色
    const roles = await this.roleService.getRolesByIdArr(reqAddUserDto.roleIds);

    reqAddUserDto.dept = dept;
    reqAddUserDto.roles = roles;
    if (reqAddUserDto.password) {
      reqAddUserDto.salt = this.sharedService.generateUUID();
      reqAddUserDto.password = this.sharedService.md5(reqAddUserDto.password + reqAddUserDto.salt);
    }
    await this.userRepository.save(reqAddUserDto);
  }

  // 编辑用户
  async updateUser(reqUpdateUserDto: ReqUpdateUserDto) {
    const dept = await this.deptService.getDeptById(reqUpdateUserDto.dept_id);
    const roles = await this.roleService.getRolesByIdArr(reqUpdateUserDto.roleIds);

    reqUpdateUserDto.dept = dept;
    reqUpdateUserDto.roles = roles;
    await this.userRepository.save(reqUpdateUserDto);
    if (await this.redis.get(`${USER_VERSION_KEY}:${reqUpdateUserDto.userId}`)) {
      await this.redis.set(`${USER_VERSION_KEY}:${reqUpdateUserDto.userId}`, 2); //调整密码版本，强制用户重新登录
    }
  }

  // 删除用户
  async deleteUser(userId: string) {
    return this.userRepository.delete(userId);
  }

  // 通过部门id查询用户
  async getUserInfoByDeptId(dept_id: string | number) {
    return await this.userRepository
      .createQueryBuilder("user")
      .innerJoin("user.dept", "dept")
      .where("dept.dept_id = :dept_id", { dept_id })
      .getRawMany();
  }
}
